// Sunghan Cho
// 301140084
// sunghanc@sfu.ca

#include "unittests.h"
#include "course.h"
#include "student.h"
#include "itemmanager.h"

#include <QDebug>

////////////////////////////////////////////////////////////
// Course Test Functions
////////////////////////////////////////////////////////////
void testCourseData()
{
    qDebug() << "Unit Test: Course -- Data";
    const QString NAME = "Hard Knocks 101";
    const QString SEMESTER = "Fall 2140";
    Course c1(NAME, SEMESTER);
    Q_ASSERT(c1.getName() == NAME);
    Q_ASSERT(c1.getSemester() == SEMESTER);
}

void testCourseItemInterface()
{
    qDebug() << "Unit Test: Course -- Item Interface";
    const QString NAME = "Hard Knocks 101";
    const QString SEMESTER = "Spring 1959";
    Item *pItem = new Course(NAME, SEMESTER);

    // Check general field-interface to access data.
    Q_ASSERT(pItem->getFieldCount() == 2);
    Q_ASSERT(pItem->getFieldHeading(0) == "Course");
    Q_ASSERT(pItem->getFieldHeading(1) == "Semester");
    Q_ASSERT(pItem->getFieldValue(0) == NAME);
    Q_ASSERT(pItem->getFieldValue(1) == SEMESTER);

    // Check it's matching ability.
    Q_ASSERT(pItem->matchesPrimaryField(NAME) == true);
    Q_ASSERT(pItem->matchesPrimaryField(SEMESTER) == false);
    Q_ASSERT(pItem->matchesPrimaryField("Garbage Text") == false);
    Q_ASSERT(pItem->matchesPrimaryField(11212112) == false);
}

////////////////////////////////////////////////////////////
// Student Test Functions
////////////////////////////////////////////////////////////
void testStudentData()
{
    qDebug() << "Unit Test: Student -- Data";

    const QString NAME = "The Big Bopper";
    const int NUMBER = 987654321;
    const QString EMAIL = "bigbop@sfu.ca";
    const QString PREF = "Jiles";
    Student s1(NAME, NUMBER, EMAIL, PREF);
    Q_ASSERT(s1.getName() == NAME);
    Q_ASSERT(s1.getStudentNumber() == NUMBER);
    Q_ASSERT(s1.getEmail() == EMAIL);
    Q_ASSERT(s1.getPreferredName() == PREF);

    // Test with 0 courses.:
    Q_ASSERT(s1.getCoursesTakenCount() == 0);
    Q_ASSERT(s1.getCoursesTakenNames() == 0);
    Q_ASSERT(s1.hasTakenCourse(0) == false);

    // Create courses :
    const QString COURSENAME = "Hard Knocks 101";
    const QString SEMESTER = "Spring 1959";
    Course c1(COURSENAME, SEMESTER);

    const QString COURSENAME2 = "Hard Knocks 201";
    const QString SEMESTER2 = "Summer 1959";
    Course c2(COURSENAME2, SEMESTER2);

    // Add a single course.
    s1.addCourse(&c1);
    Q_ASSERT(s1.getCoursesTakenCount() == 1);
    Q_ASSERT(s1.getCoursesTakenNames() == COURSENAME);
    Q_ASSERT(s1.hasTakenCourse(0) == false);
    Q_ASSERT(s1.hasTakenCourse(&c1) == true);
    Q_ASSERT(s1.hasTakenCourse(&c2) == false);

    // Add a second course
    s1.addCourse(&c2);
    Q_ASSERT(s1.getCoursesTakenCount() == 2);
    Q_ASSERT(s1.getCoursesTakenNames() == COURSENAME + ", " + COURSENAME2);
    Q_ASSERT(s1.hasTakenCourse(0) == false);
    Q_ASSERT(s1.hasTakenCourse(&c1) == true);
    Q_ASSERT(s1.hasTakenCourse(&c2) == true);
}

void testStudentItemInterface()
{
    qDebug() << "Unit Test: Student -- ItemInterface";

    const QString NAME = "The Big Bopper";
    const int NUMBER = 987654321;
    const QString EMAIL = "bigbop@sfu.ca";
    const QString PREF = "Jiles";
    Item *pItem = new Student(NAME, NUMBER, EMAIL, PREF);

    // Check general field-interface to access data.
    Q_ASSERT(pItem->getFieldCount() == 3);
    Q_ASSERT(pItem->getFieldHeading(0) == "Name");
    Q_ASSERT(pItem->getFieldHeading(1) == "Student #");
    Q_ASSERT(pItem->getFieldHeading(2) == "Courses");
    Q_ASSERT(pItem->getFieldValue(0) == NAME);
    Q_ASSERT(pItem->getFieldValue(1) == NUMBER);
    Q_ASSERT(pItem->getFieldValue(2) == "");

    // Check it's matching ability.
    Q_ASSERT(pItem->matchesPrimaryField(NUMBER) == true);
    Q_ASSERT(pItem->matchesPrimaryField(NAME) == false);
    Q_ASSERT(pItem->matchesPrimaryField("Garbage Text") == false);
    Q_ASSERT(pItem->matchesPrimaryField(11212112) == false);
}

////////////////////////////////////////////////////////////
// ItemManager Test Functions
////////////////////////////////////////////////////////////
void testItemManager()
{
    qDebug() << "Unit Test: ItemManager";
    ItemManager items;

    const QString COURSENAME = "Hard Knocks 101";
    const QString SEMESTER = "Spring 1959";
    Course *pC1 = new Course(COURSENAME, SEMESTER);

    const QString NAME = "The Big Bopper";
    const int NUMBER = 987654321;
    const QString EMAIL = "bigbop@sfu.ca";
    const QString PREF = "Jiles";
    Student *pS1 = new Student(NAME, NUMBER, EMAIL, PREF);
    pS1->addCourse(pC1);


    // Test empty
    Q_ASSERT(items.getItemCount() == 0);
    QListIterator<Item*> itr0 = items.getIterator();
    Q_ASSERT(itr0.hasNext() == false);

    // Test one item
    items.addItem(pS1);
    Q_ASSERT(items.getItemCount() == 1);
    QListIterator<Item*> itr1 = items.getIterator();
    Q_ASSERT(itr1.hasNext() == true);
    Q_ASSERT(itr1.next() == pS1);
    Q_ASSERT(itr1.hasNext() == false);
    Q_ASSERT(items.findMatchingItem(NUMBER) == pS1);
    Q_ASSERT(items.findMatchingItem("") == 0);

    // Test two items
    items.addItem(pC1);
    Q_ASSERT(items.getItemCount() == 2);
    QListIterator<Item*> itr2 = items.getIterator();
    Q_ASSERT(itr2.hasNext() == true);
    Q_ASSERT(itr2.next() == pS1);
    Q_ASSERT(itr2.hasNext() == true);
    Q_ASSERT(itr2.next() == pC1);
    Q_ASSERT(itr2.hasNext() == false);
    Q_ASSERT(items.findMatchingItem(NUMBER) == pS1);
    Q_ASSERT(items.findMatchingItem("") == 0);
    Q_ASSERT(items.findMatchingItem(COURSENAME) == pC1);
    Q_ASSERT(items.findMatchingItem("Guess") == 0);

    // Test debug dump:
    // NOTE: Check the qDebug() console output for the output.
    items.debugDumpData();

    // NOTE: Signal "itemChanged()" untested.
}













